﻿using Frame.Core.Attribute;
using Frame.Core.Auth;
using Frame.Core.Common.Auth;
using Frame.Core.Common.Cache;
using Frame.Core.Common.Extensions;
using Frame.Core.Common.Hubs;
using Frame.Core.Models;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.SignalR;
using Microsoft.Extensions.Hosting;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Linq.Expressions;
using System.Security.Claims;
using System.Threading.Tasks;

namespace Frame.Core.Controllers
{
    [Authorize]
    public class TaskCenterController : BaseController
    {
        readonly IUser _user;
        readonly IPermissionHandler _permissionHandler;
        readonly ICache _cache;
        readonly IFreeSql _freeSql;
        readonly IHubContext<ChatHub> _hubContext;
        readonly IHostEnvironment _env;
        public TaskCenterController(IUser user, IHostEnvironment env, ICache cache, IPermissionHandler permissionHandler,IFreeSql freeSql, IHubContext<ChatHub> hubContext)
        {
            _user = user;
            _cache = cache;
            _env = env;
            base.onlineService = onlineService;
            _permissionHandler = permissionHandler;
            _hubContext = hubContext;
            _freeSql = freeSql;
        }

        #region 任务管理
        [CheckPower(Name = "CoreTaskSchedulingView")]
        public async Task<IActionResult> TaskSchedulingList()
        {
            ViewBag.CoreTaskSchedulingDelete = await _permissionHandler.CheckPower("CoreTaskSchedulingDelete");
            if (Convert.ToInt32(_user.TaskRoleId)==(int)BillTypeEnum.TaskRoleLaunch)//发起方，有新增权限
            {
                ViewBag.CoreTaskSchedulingNew = true;
                ViewBag.CoreTaskSchedulingLaunch = true;
                ViewBag.CoreTaskSchedulingResult = false;
            }
            else if(Convert.ToInt32(_user.TaskRoleId) == (int)BillTypeEnum.TaskRoleReceive)//接收方有回复权限
            {
                ViewBag.CoreTaskSchedulingNew = false;
                ViewBag.CoreTaskSchedulingLaunch = false;
                ViewBag.CoreTaskSchedulingResult = true;
            }
            else
            {
                ViewBag.CoreTaskSchedulingNew = false;
                ViewBag.CoreTaskSchedulingLaunch = false;
                ViewBag.CoreTaskSchedulingResult = false;
            }
            return View();
        }
        [HttpPost]
        public async Task<IActionResult> GetTaskSchedulingListJson(int page, int limit, string key, string field, string order,
    string Customer, string startEndDate, int ReadStatus, string ResultStatus)
        {
            Expression<Func<TaskScheduling, bool>> whereExpression = null;
            if (Convert.ToInt32(_user.TaskRoleId) == (int)BillTypeEnum.TaskRoleLaunch)//发起方，有新增权限
            {
                whereExpression = whereExpression.And(a=>a.LaunchId==_user.Id);
            }
            else if (Convert.ToInt32(_user.TaskRoleId) == (int)BillTypeEnum.TaskRoleReceive)//接收方有回复权限
            {
                whereExpression = whereExpression.And(a => a.ReceiveId == _user.Id);
            }
            if (!string.IsNullOrWhiteSpace(Customer))
            {
                whereExpression = whereExpression.And(a => a.Customer.Contains(Customer));
            }

            if (!string.IsNullOrEmpty(startEndDate))
            {
                var arr = startEndDate.Split("~");

                whereExpression = whereExpression.And(a => a.LaunchTime.Between(Convert.ToDateTime(arr[0].Trim()), Convert.ToDateTime(arr[1].Trim())));
            }

            if (ReadStatus != -1)
            {
                var boolReadStatus = Convert.ToBoolean(ReadStatus);
                whereExpression = whereExpression.And(a => a.ReadStatus == boolReadStatus);
            }
            if (ResultStatus != "-1")
            {
                if (ResultStatus == "1")
                {
                    whereExpression = whereExpression.And(a => a.ResultStatus != (int)BillTypeEnum.ResultWait);
                }
                else
                {
                    whereExpression = whereExpression.And(a => a.ResultStatus == (int)BillTypeEnum.ResultWait);
                }
                
            }
            order ??= "asc";
            var pagingInfo = new PagingInfoViewModel<TaskScheduling>
            {
                PageKey = a => a.Id,
                SortField = field,
                Descending = order == "asc",
                PageIndex = page,
                PageSize = limit
            };

            var list = await _freeSql.Select<TaskScheduling>()
                .OrderByPropertyNameIf(pagingInfo.SortField != null, pagingInfo.SortField, pagingInfo.Descending).OrderBy(pagingInfo.PageKey)
                .Include(a=>a.Users_Launch)
                .Include(a=>a.Users_Receive)
                .Include(a=>a.Navigate_ResultStatus)
                .WhereIf(whereExpression!=null, whereExpression)
                .Count(out var total)
                .Page(pagingInfo.PageIndex, pagingInfo.PageSize)
                .ToListAsync();
            pagingInfo.Count = total;

            return Json(new LayuiTableDataAjaxResult { code = 0, msg = "", codeIndex = 1, count = pagingInfo.Count, data = list });
        }

        [HttpPost]
        [ValidateAntiForgeryToken]
        [CheckPower(Name = "CoreTaskSchedulingDelete")]
        public async Task<IActionResult> DeleteTaskSchedulingAsync(int[] ids)
        {
            var result = new AjaxResult { codeIndex = 1, msg = "成功！" };
            try
            {
                var list = await _freeSql.Select<TaskScheduling>().Where(a => ids.Contains(a.Id)).ToListAsync();
                foreach (var item in list)
                {
                    if (!string.IsNullOrEmpty(item.LaunchPicUrl))
                    {
                        string server_LaunchPicUrl = _env.ContentRootPath + item.LaunchPicUrl;
                        //删除文件
                        if (System.IO.File.Exists(server_LaunchPicUrl))//判断文件是否存在
                        {
                            System.IO.File.Delete(server_LaunchPicUrl);//执行IO文件删除,需引入命名空间System.IO;
                        }
                    }
                    if (!string.IsNullOrEmpty(item.ReceivePicUrl))
                    {
                        string server_ReceivePicUrl = _env.ContentRootPath + item.ReceivePicUrl;
                        //删除文件
                        if (System.IO.File.Exists(server_ReceivePicUrl))//判断文件是否存在
                        {
                            System.IO.File.Delete(server_ReceivePicUrl);//执行IO文件删除,需引入命名空间System.IO;
                        }
                    }
                }
                await _freeSql.Delete<TaskScheduling>().Where(a => ids.Contains(a.Id)).ExecuteAffrowsAsync();
                return Json(result);
            }
            catch (Exception ex)
            {
                result.codeIndex = -1;
                result.msg = "错误：" + ex.Message;
                return Json(result);
            }
        }

        #endregion

        #region TaskSchedulingNew

        public IActionResult TaskSchedulingNew()
        {
            if (Convert.ToInt32(_user.TaskRoleId) != (int)BillTypeEnum.TaskRoleLaunch)//发起方，有新增权限
            {
                return Content("当前用户任务权限不是发起人,不能新增");
            }
            return View();
        }

        [ValidateAntiForgeryToken]
        public async Task<IActionResult> TaskSchedulingNew_btnSaveClose_Click(string Customer,decimal LaunchAmount,string LaunchRemark)
        {
            if (Convert.ToInt32(_user.TaskRoleId) != (int)BillTypeEnum.TaskRoleLaunch)//发起方，有新增权限
            {
                return Json(new AjaxResult { codeIndex = -1, msg = "当前用户任务权限不是发起人,不能新增！" });
            }

            try
            {
                var file = Request.Form.Files[0]; //获取选中文件 
                if (file != null)
                {
                    //获取文件后缀
                    string fileType = String.Empty;
                    int lastDotIndex = file.FileName.LastIndexOf(".");
                    if (lastDotIndex >= 0)
                    {
                        fileType = file.FileName.Substring(lastDotIndex + 1).ToLower();
                    }
                    //文件路径
                    string strFilePath= $"/staticFiles/upLoadFiles/{DateTimeExtensions.ToTimestamp(DateTime.Now)}{file.FileName}";
                    //获取服务器路径+文件
                    string server_strFilePath = $"{_env.ContentRootPath}/{strFilePath}";

                    //查询对应接收人
                    var UserTaskRoleReceive = await _freeSql.Select<Users>().Where(a => a.DeptID == Convert.ToInt32(_user.DeptId) && a.TaskRoleId == (int)BillTypeEnum.TaskRoleReceive).ToOneAsync();
                    if (UserTaskRoleReceive is null)
                    {
                        return Json(new AjaxResult { codeIndex = -1, msg = "无接收人，请联系管理员！" });
                    }
                    using (var stream = new FileStream(server_strFilePath, FileMode.Create))
                    {
                        file.CopyTo(stream);
                    }
                    var obj = new TaskScheduling {
                        Customer = Customer,
                        LaunchAmount = LaunchAmount,
                        LaunchRemark = LaunchRemark,
                        LaunchPicUrl= strFilePath,
                        Status=true,
                        ReadStatus = false,
                        ResultStatus = (int)BillTypeEnum.ResultWait,
                        LaunchId = _user.Id,
                        ReceiveId = UserTaskRoleReceive.ID,
                        LaunchTime = DateTime.Now
                    };
                    await _freeSql.Insert<TaskScheduling>(obj).ExecuteAffrowsAsync();

                    var count=_freeSql.Select<TaskScheduling>().Where(a => a.ReceiveId == UserTaskRoleReceive.ID && a.ResultStatus == (int)BillTypeEnum.ResultWait).ToList(a => a.Id).Count;
                    await _hubContext.Clients.User(obj.ReceiveId.ToString()).SendAsync("ReceiveMessage", true, count.ToString());
                    return Json(new AjaxResult { codeIndex = 1, msg = "发送任务成功" });
                }
                else
                {
                    return Json(new AjaxResult { codeIndex = -1, msg = "未获取到上传文件！" });
                }
            }
            catch (Exception e)
            {
                return Json(new AjaxResult { codeIndex = -1, msg = e.Message });
            }
        }

        #endregion

        #region TaskSchedulingResult

        public IActionResult TaskSchedulingResult(int id)
        {
            if (Convert.ToInt32(_user.TaskRoleId) != (int)BillTypeEnum.TaskRoleReceive)//发起方，有新增权限
            {
                return Content("当前用户任务权限不是接收人,不能回复");
            }

            var obj = _freeSql.Select<TaskScheduling>().Include(a=>a.Navigate_ResultStatus).Where(a => a.Id == id).ToOne();
            return View(obj);
        }

        [HttpPost]
        [ValidateAntiForgeryToken]
        public async Task<IActionResult> TaskSchedulingResult_Update(int id, decimal ReceiveAmount, string ReceiveRemark)
        {
            if (Convert.ToInt32(_user.TaskRoleId) != (int)BillTypeEnum.TaskRoleReceive)//发起方，有新增权限
            {
                return Json(new AjaxResult { codeIndex = -1, msg = "当前用户任务权限不是接收人,不能回复！" });
            }

            var repo = _freeSql.GetRepository<TaskScheduling>();
            var obj = repo.Where(a => a.Id == id).ToOne();
            if (obj is null)
            {
                return Json(new AjaxResult { codeIndex = -1, msg = "信息不存在" });
            }
            if (obj.ResultStatus != (int)BillTypeEnum.ResultWait)
            {
                return Json(new AjaxResult { codeIndex = -1, msg = "任务已经回复" });
            }

            try
            {
                var file = Request.Form.Files[0]; //获取选中文件 
                if (file != null)
                {
                    //获取文件后缀
                    string fileType = String.Empty;
                    int lastDotIndex = file.FileName.LastIndexOf(".");
                    if (lastDotIndex >= 0)
                    {
                        fileType = file.FileName.Substring(lastDotIndex + 1).ToLower();
                    }
                    //文件路径
                    string strFilePath = $"/staticFiles/upLoadFiles/{DateTimeExtensions.ToTimestamp(DateTime.Now)}{file.FileName}";
                    //获取服务器路径+文件
                    string server_strFilePath = $"{_env.ContentRootPath}/{strFilePath}";

                    using (var stream = new FileStream(server_strFilePath, FileMode.Create))
                    {
                        file.CopyTo(stream);
                    }


                    obj.ResultStatus = (int)BillTypeEnum.ResultYes;
                    obj.ReceivePicUrl = strFilePath;
                    obj.ReceiveAmount = ReceiveAmount;
                    obj.ReceiveRemark = ReceiveRemark;
                    obj.ResultTime = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");

                    repo.Update(obj);

                    //获取未读消息条数
                    var messageCount = _freeSql.Select<TaskScheduling>().Where(a => a.LaunchId == obj.LaunchId && a.ResultStatus != (int)BillTypeEnum.ResultWait && a.ReadStatus == false).ToList(a => a.Id).Count;
                    await _hubContext.Clients.User(obj.LaunchId.ToString()).SendAsync("ReceiveMessage", true, messageCount.ToString());

                    //获取未读消息条数
                    var messageReceiveIdCount = _freeSql.Select<TaskScheduling>().Where(a => a.ReceiveId == obj.ReceiveId && a.ResultStatus == (int)BillTypeEnum.ResultWait).ToList(a => a.Id).Count;

                    await _hubContext.Clients.User(obj.ReceiveId.ToString()).SendAsync("ReceiveMessage", false, messageReceiveIdCount.ToString());

                    return Json(new AjaxResult { codeIndex = 1, msg = "回复成功" });
                }
                else
                {
                    return Json(new AjaxResult { codeIndex = -1, msg = "未获取到上传文件！" });
                }
            }
            catch (Exception e)
            {
                return Json(new AjaxResult { codeIndex = -1, msg = e.Message });
            }
        }

        [HttpPost]
        [ValidateAntiForgeryToken]
        public async Task<IActionResult> TaskSchedulingResultNo_Update(int id,string ReceiveRemark)
        {
            if (Convert.ToInt32(_user.TaskRoleId) != (int)BillTypeEnum.TaskRoleReceive)//发起方，有新增权限
            {
                return Json(new AjaxResult { codeIndex = -1, msg = "当前用户任务权限不是接收人,不能回复！" });
            }

            var repo = _freeSql.GetRepository<TaskScheduling>();
            var obj = repo.Where(a => a.Id == id).ToOne();
            if (obj is null)
            {
                return Json(new AjaxResult { codeIndex = -1, msg = "信息不存在" });
            }
            if (obj.ResultStatus != (int)BillTypeEnum.ResultWait)
            {
                return Json(new AjaxResult { codeIndex = -1, msg = "任务已经回复" });
            }

            obj.ResultStatus = (int)BillTypeEnum.ResultNo;
            obj.ReceiveRemark = ReceiveRemark;
            obj.ResultTime = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");

            repo.Update(obj);

            //获取未读消息条数
            var messageCount = _freeSql.Select<TaskScheduling>().Where(a => a.LaunchId == obj.LaunchId && a.ResultStatus != (int)BillTypeEnum.ResultWait && a.ReadStatus == false).ToList(a => a.Id).Count;
            await _hubContext.Clients.User(obj.LaunchId.ToString()).SendAsync("ReceiveMessage", true, messageCount.ToString());

            //获取未读消息条数
            var messageReceiveIdCount = _freeSql.Select<TaskScheduling>().Where(a => a.ReceiveId == obj.ReceiveId && a.ResultStatus == (int)BillTypeEnum.ResultWait).ToList(a => a.Id).Count;

            await _hubContext.Clients.User(obj.ReceiveId.ToString()).SendAsync("ReceiveMessage", false, messageReceiveIdCount.ToString());

            return Json(new AjaxResult { codeIndex = 1, msg = "回复成功" });
        }

        #endregion


        #region TaskSchedulingResult

        public async Task<IActionResult> TaskSchedulingRead(int id)
        {
            var obj = _freeSql.Select<TaskScheduling>().Include(a => a.Navigate_ResultStatus).Where(a => a.Id == id).ToOne();
            if (obj.LaunchId==_user.Id)
            {
                if (obj.ResultStatus!= (int)BillTypeEnum.ResultWait && obj.ReadStatus == false)
                {
                    _freeSql.Update<TaskScheduling>()
                        .Set(a => a.ReadStatus, true)
                        .Set(a => a.ResultReadTime, DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"))
                        .Where(a => a.Id == obj.Id)
                        .ExecuteAffrows();
                    //获取未读消息条数
                    var messageCount = _freeSql.Select<TaskScheduling>().Where(a => a.LaunchId == obj.LaunchId && a.ResultStatus != (int)BillTypeEnum.ResultWait && a.ReadStatus == false).ToList(a => a.Id).Count;
                    await _hubContext.Clients.User(obj.LaunchId.ToString()).SendAsync("ReceiveMessage", false, messageCount.ToString());
                }
            }
            return View(obj);
        }

        #endregion


    }
}